package entities.concept;

//import java.util.HashSet;
import java.util.HashSet;
import java.util.Set;

import option.KBVocabulary;

import utils.Display;

import entities.KBEntity;
import entities.role.Role;

public final class NotConcept extends Concept {
	private final Concept con;

	public NotConcept(Concept con) {
		this.con = con;
	}

	public Concept getConcept() {
		return this.con;
	}

	private volatile int hashCode = 0;

	@Override
	public int hashCode() {
		if (hashCode != 0) {
			return hashCode;
		}
		final int prime = 31;
		int result = 1 + KBVocabulary.NOT.hashCode();
		result = prime * result + ((con == null) ? 0 : con.hashCode());
		hashCode = result;
		return result;
	}

	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (!(obj instanceof NotConcept))
			return false;
		NotConcept other = (NotConcept) obj;
		if (con == null) {
			if (other.con != null)
				return false;
		} else if (!con.equals(other.con))
			return false;
		return true;
	}

	@Override
	public String toString() {
		return Display.NOTUNICODE + " " + con.toString() + "";
	}

	@Override
	public Concept getPrimeCopy() {
		return new NotConcept(con.getPrimeCopy());
	}

	public String toSerializedString() {
		return " (" + KBVocabulary.NOT + " " + this.con.toSerializedString()
				+ ") ";
	}

	@Override
	public Set<Role> extractFeatures() {
		return this.con.extractFeatures();
	}

	@Override
	public Set<Role> extractRoles() {
		return this.con.extractRoles();
	}

	@Override 
	public Set<KBEntity> extractSig(){
		Set<KBEntity> sig = new HashSet<KBEntity>();
		sig.addAll(this.con.extractSig());
		return sig;
	}
	@Override
	public Set<String> extractConstants() {
		Set<String> ks = new HashSet<String>();
		ks.addAll(this.con.extractConstants());
		return ks;
	}

	@Override
	public Set<AtomicConcept> extracAtomicConcepts() {
		Set<AtomicConcept> cs = new HashSet<AtomicConcept>();
		cs.addAll(this.con.extracAtomicConcepts());
		return cs;
	}

	@Override
	public boolean isParameterized() {
		return this.con.isParameterized();
	}

	@Override
	public Concept makeParameterized() {
		return new NotConcept(this.con.makeParameterized());
	}

	@Override
	public Concept initParameters(Role f, String v) {
		return new NotConcept(this.con.initParameters(f, v));
	}

	@Override
	//note that this method is problematic for negation, if NNF is applied, this should return false.
	public boolean hasUniversalInside() {
		return this.con.hasUniversalInside();
	}
	

}
